package org.hawk.gwt.ppc.introspection.impl;

import java.lang.reflect.Field;
import java.util.List;

import org.hawk.gwt.ppc.introspection.JavaField;
import org.hawk.gwt.ppc.introspection.JavaModifier;
import org.hawk.gwt.ppc.introspection.JavaTypeScope;
import org.hawk.gwt.ppc.parser.ModificatedDescriptor;
import org.hawk.gwt.ppc.parser.VariableDescriptor;

/**
 * Java field implementation.
 * 
 * @author alex.bereznevatiy@gmail.com
 *
 */
final class JavaFieldImpl extends JavaVariableImpl implements JavaField {
	
	private Field field;
	private String name;
	private String type;

	JavaFieldImpl(VariableDescriptor descriptor, AbstractJavaTypeScope scope) {
		super(descriptor, scope);
	}
	
	List<JavaModifier> setModifiers(ModificatedDescriptor descriptor) {
		List<JavaModifier> result = super.setModifiers(descriptor);
		AbstractJavaTypeScope type = (AbstractJavaTypeScope) getScope();
		if (type.isInterface()) {
			if (!result.contains(JavaModifier.PUBLIC)) result.add(JavaModifier.PUBLIC);
			if (!result.contains(JavaModifier.STATIC)) result.add(JavaModifier.STATIC);
			if (!result.contains(JavaModifier.FINAL)) result.add(JavaModifier.FINAL);
		}
		setModifiers(result);
		return result;
	}

	JavaFieldImpl(Field field, JavaScopeImpl scope) {
		super(null, scope);
		
		this.field = field;
		setModifiers(JavaModifier.fromMask(field.getModifiers()));
	}

	JavaFieldImpl(String name, String type,
			JavaScopeImpl scope) {
		super(null, scope);
		this.name = name;
		this.type = type;
	}

	/* (non-Javadoc)
	 * @see org.hawk.gwt.ppc.introspection.impl.JavaVariableImpl#getName()
	 */
	@Override
	public String getName() {
		if (name != null) {
			return name;
		}
		if (field == null) {
			return super.getName();
		}
		return field.getName();
	}
	
	/*
	 * (non-Javadoc)
	 * @see org.hawk.gwt.ppc.introspection.impl.JavaVariableImpl#resolveType()
	 */
	JavaTypeScope resolveType() {
		if (type != null) {
			return getScope().resolveType(type, null);
		}
		if (field == null) {
			return super.resolveType();
		}
		return GenericHelper.buildGenericType(field.getGenericType(), getScope());		
	}
}
